package database

import (
	"database/sql"
	"fmt"
	"log"
	"strconv"
	"time"

	_ "github.com/go-sql-driver/mysql"
)

type Mysql struct {
	DbName   string
	Username string
	Password string
	Address  string
	Port     int
	Handler  *sql.DB
}

var MysqlClient = &Mysql{}

func init() {
	MysqlClient.Connect("metameeting_interact", "metameeting_interact", "6FBnoPmI9!5d", "10.124.130.52", 3306)
}


func (mysql *Mysql) Connect(dbname string, username string, password string, address string, port int) error {
	db, err := sql.Open("mysql", fmt.Sprintf("%s:%s@tcp(%s:%d)/%s", username, password, address, port, dbname))
	if err == nil {
		mysql.Handler = db
	}
	return err
}

func (mysql *Mysql) Close() {
	if mysql.Handler != nil {
		mysql.Handler.Close()
	}
}

func (mysql *Mysql) ExecuteQuery(sql string) [][]any {
	rows, err := mysql.Handler.Query(sql) // 执行 SQL 语句
	if err != nil {
		log.Fatal(err)
	}
	defer rows.Close()

	var out = make([][]any, 0)

	// 获取列名
	columns, err := rows.Columns()
	if err != nil {
		log.Fatal(err)
	}

	// 获取每列的数据类型
	types := make([]string, len(columns))
	colsType, err := rows.ColumnTypes()

	for i, colType := range colsType {
		var typ string
		switch colType.DatabaseTypeName() {
		case "INT":
			typ = "int"
		case "VARCHAR":
			typ = "string"
		case "DATETIME":
			typ = "time.Time"
		default: 		// 添加其他类型映射
			typ = "unknown"
		}
		types[i] = typ
	}

	// 打印表头
	fmt.Println("Columns:", columns)

	// 遍历结果集
	for rows.Next() {
		row := make([]any, len(columns))
		// 创建一个切片来存储结果
		values := make([]interface{}, len(columns))
		scanArgs := make([]interface{}, len(columns))
		for i := range values {
			values[i] = new(interface{})
			scanArgs[i] = values[i]
		}

		if err := rows.Scan(scanArgs...); err != nil {
			log.Println(err)
			return out
		}

		for i, value := range values {
			actualValue := *value.(*interface{})
			switch v := actualValue.(type) {
			case int64:
				row[i] = strconv.Itoa(int(v))
			case string:
				row[i] = v
			case time.Time:
				row[i] = v.Format("2006-01-02 15:04:05")
			case []uint8:
				row[i] = string(v)
			default:
				row[i] = actualValue
			}
		}

		out = append(out, row)
	}

	return out
}

func MysqlMain() {
	// 连接到 MySQL 数据库
	db, err := sql.Open("mysql", "metameeting_interact:6FBnoPmI9!5d@tcp(10.124.130.52:3306)/metameeting_interact")
	if err != nil {
		log.Fatal(err)
	}
	defer db.Close()

	// 执行 SQL 语句
	rows, err := db.Query("SELECT * FROM mcc_bag limit 1")
	if err != nil {
		log.Fatal(err)
	}
	defer rows.Close()

	// 获取列名
	columns, err := rows.Columns()
	if err != nil {
		log.Fatal(err)
	}

	// 获取每列的数据类型
	types := make([]string, len(columns))
	colsType, err := rows.ColumnTypes()

	for i, colType := range colsType {
		var typ string
		switch colType.DatabaseTypeName() {
		case "INT":
			typ = "int"
		case "VARCHAR":
			typ = "string"
		case "DATETIME":
			typ = "time.Time"
		// 添加其他类型映射
		default:
			typ = "unknown"
		}
		types[i] = typ
	}

	// 打印表头
	fmt.Println("Columns:", columns)

	// 遍历结果集
	for rows.Next() {
		// 创建一个切片来存储结果
		values := make([]interface{}, len(columns))
		scanArgs := make([]interface{}, len(columns))
		for i := range values {
			values[i] = new(interface{})
			scanArgs[i] = values[i]
		}

		// 扫描行数据
		if err := rows.Scan(scanArgs...); err != nil {
			log.Fatal(err)
		}

		// 打印行数据
		fmt.Println("Row:")
		for i, value := range values {
			switch v := (value).(type) {
			case int64:
				fmt.Printf("%s (%s): %d\n", columns[i], types[i], v)
			case string:
				fmt.Printf("%s (%s): %s\n", columns[i], types[i], v)
			case time.Time:
				fmt.Printf("%s (%s): %s\n", columns[i], types[i], v.Format("2006-01-02 15:04:05"))
			default:
				fmt.Printf("%s (%s): %v\n", columns[i], types[i], v)
			}
		}
	}

	// 检查遍历过程中是否有错误
	if err = rows.Err(); err != nil {
		log.Fatal(err)
	}
}
